package simco.framework.gui.services.data;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import simco.framework.gui.graph.ConnectingLine;
import simco.framework.gui.graph.base.GraphObject;
import simco.framework.gui.services.ChangeEventSupporter;

/**
 * Tato trida reprezentuje datovy model grafu (vizualizovanych
 * komponent a vazeb mezi nimi). Trida zapouzdruje
 * vsechny vizualizovane objekty na platne a informace
 * o rozmerech platna.
 * 
 * @author Matej Prokop, mythge@students.zcu.cz
 *
 */
public class GraphModel extends ChangeEventSupporter
{
	/**
	 * Seznam vizualizovanych grafickych objektu
	 */
	private List<GraphObject> graphObjects;
	
	/**
	 * Seznam vazeb mezi vizualizovanymi objekty
	 */
	private List<ConnectingLine> connLines;
	
	/**
	 * Mapa vizualizovanych grafickych objektu
	 */
	private Map<Long, GraphObject> objectMap;
	
	/**
	 * Mapa vazeb mezi vizualizovanymi objekty
	 */
	private Map<Long, ConnectingLine> connMap;
	
	/**
	 * Sirka platna
	 */
	private int canvasWidth;
	
	/**
	 * Vyska platna
	 */
	private int canvasHeight;
	
	/**
	 * Vytvori novy datovy model vizualizovaneho grafu
	 */
	public GraphModel()
	{
		connLines = new ArrayList<ConnectingLine>();
        graphObjects = new ArrayList<GraphObject>();
        objectMap = new HashMap<Long, GraphObject>();
        connMap = new HashMap<Long, ConnectingLine>();
	}
	
	/**
	 * Prida vazbu do modelu grafu
	 * 
	 * @param line pridavana vazba mezi objekty
	 */
	public void addLine(ConnectingLine line)
	{
		this.connLines.add(line);
		this.connMap.put(line.getId(), line);
	}
	
	/**
	 * Prida graficky objekt do modelu grafu
	 * 
	 * @param object pridavany graficky objekt
	 */
	public void addObject(GraphObject object)
	{
		this.graphObjects.add(object);
		this.objectMap.put(object.getId(), object);
	}
	
	/**
	 * Vrati graficky objekt podle identifikatoru
	 * 
	 * @param id identifikator pozadovaneho objektu
	 * @return odpovidajici graficky objekt
	 */
	public GraphObject getObjectById(long id)
	{
		return this.objectMap.get(id);
	}	
	
	/**
	 * Vrati seznam vizualizovanych grafickych objektu
	 * @return seznam vizualizovanych grafickych objektu
	 */
	public List<GraphObject> getGraphObjects() {
		return graphObjects;
	}

	/**
	 * Vrati seznam vazeb mezi vizualizovanymi objekty
	 * @return seznam vazeb mezi vizualizovanymi objekty
	 */
	public List<ConnectingLine> getConnLines() {
		return connLines;
	}
	
	/**
	 * Odstrani vsechny objekty a vazby z modelu
	 */
	public void restartModel()
	{
		connLines.clear();
        graphObjects.clear();
        objectMap.clear();
        connMap.clear();		
	}
	
	/**
	 * Vrati sirku platna 
	 * @return sirka platna
	 */
	public int getCanvasWidth() 
	{
		return canvasWidth;
	}

	/**
	 * Nastavi sirku platna
	 * @param canvasWidth nova sirka plant
	 */
	public void setCanvasWidth(int canvasWidth) 
	{
		this.canvasWidth = canvasWidth;
	}

	/**
	 * Vrati vysku platna
	 * @return vyska platna
	 */
	public int getCanvasHeight() 
	{
		return canvasHeight;
	}

	/**
	 * Nastavi vysku platna
	 * @param canvasHeight nova vyska platna
	 */
	public void setCanvasHeight(int canvasHeight) 
	{
		this.canvasHeight = canvasHeight;
	}

	/**
	 * Vrati mapu vsech pridanych vazeb mezi objekty
	 * @return mapu vsech pridanych vazeb mezi objekty
	 */
	public Map<Long, ConnectingLine> getConnMap() 
	{
		return connMap;
	}

	/**
	 * Provede aktualizovany modelu na platne
	 */
	public void publichChanges()
	{
		this.fireStateChanged();
	}
}

